package com.syl.practice.serialize;

import org.junit.Assert;

import java.io.*;

/**
 *
 * 详情见：https://www.cnblogs.com/9dragon/p/10901448.html
 *
 * 1. 所有需要网络传输的对象都需要实现序列化接口，通常建议所有的javaBean都实现Serializable接口。
 * 2. 对象的类名、实例变量（包括基本类型，数组，对其他对象的引用）都会被序列化；方法、类变量、transient实例变量都不会被序列化。
 * 3. 如果想让某个变量不被序列化，使用transient修饰。
 * 4. 序列化对象的引用类型成员变量，也必须是可序列化的，否则，会报错。
 * 5. 反序列化时必须有序列化对象的class文件。
 * 6. 当通过文件、网络来读取序列化后的对象时，必须按照实际写入的顺序读取。
 * 7. 单例类序列化，需要重写readResolve()方法；否则会破坏单例原则。
 * 8. 同一对象序列化多次，只有第一次序列化为二进制流，以后都只是保存序列化编号，不会重复序列化。
 * 9. 建议所有可序列化的类加上serialVersionUID 版本号，方便项目升级。
 *
 */
public class SerializablePrac {

    public static void main(String[] args) {
        //testSerializable();
        test2();
    }

    public static void testSerializable() {
        try {
            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            ObjectOutputStream oos = new ObjectOutputStream(baos);

            User user1 = new User();
            user1.setName("binarylei");
            oos.writeObject(user1);
            byte[] bytes = baos.toByteArray();
            System.out.println(bytes.length);               // length=89

            ByteArrayInputStream bais = new ByteArrayInputStream(bytes);
            ObjectInputStream ois = new ObjectInputStream(bais);
            User user2 = (User) ois.readObject();
            Assert.assertEquals(user1.getName(), user2.getName());  // 反序列化后保存了 User.name 信息
            Assert.assertNotEquals(user1, user2);                   // 反序列化后不是同一个对象
            System.out.println(user2.toString());

            oos.close();
            ois.close();
        } catch (IOException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }

    public static void test2() {

        try {
            User user1 = new User();
            user1.setName("binarylei");

            ObjectOutputStream oos = new ObjectOutputStream(new FileOutputStream("object.txt"));
            oos.writeObject(user1);

            ObjectInputStream ois = new ObjectInputStream(new FileInputStream("object.txt"));
            User brady = (User) ois.readObject();
            System.out.println(brady);

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

}
